home *** CD-ROM | disk | FTP | other *** search
/ Just Call Me Internet / Just Call Me Internet.iso / prog / atari / c / stut_src / exformdo.c < prev    next >
C/C++ Source or Header  |  1996-05-27  |  21KB  |  1,014 lines

  1. /*
  2.  * exformdo.c
  3.  *
  4.  * Purpose:
  5.  * --------
  6.  * Form_Do GEM ‚tendu
  7.  *
  8.  * History:
  9.  * --------
  10.  * 1993: fplanque: Created
  11.  */
  12.  
  13.      #include "!OPTIONS.H"                /* Options de compilation */         
  14.     #define    THIS_FILE    "EXFORMDO.C v1.00 - 03.95"
  15.            
  16.  
  17. /*
  18.  * System headers:
  19.  */
  20.     #include <aes.h>
  21.     #include <vdi.h>
  22.     #include <stdio.h>
  23.     #include <string.h>
  24.    
  25.  
  26. /*
  27.  * Custom headers:
  28.  */
  29.     #include    "SPEC_PU.H"
  30.     #include    "TEXT_PU.H"
  31.     #include    "STKEYMAP.H"    
  32.     #include    "VDI_PU.H"    
  33.     #include "OBJCT_PU.H"
  34.     #include "EXFRM_PU.H"
  35.  
  36. /*
  37.  * ------------------------ PROTOTYPES -------------------------
  38.  */
  39.  
  40.  
  41. /*
  42.  * PRIVate INTernal prototypes:
  43.  */
  44.     /* 
  45.      * Hot Spots: 
  46.      */
  47.     int    form_dohot( OBJECT *tree, int hotobj, int mouse_x, int mouse_y, GRECT *rect, int *mode );
  48.     int    breakobj( OBJECT *tree, int obj );
  49.     int    breakx( int *pxy );
  50.     int    breaky( int *pxy );
  51.     int    inside( int x, int y, GRECT *pt );
  52.     /* 
  53.      * Clavier: 
  54.      */
  55.     int    form_dokeybd( OBJECT *tree, int editobj, int kr, int keystate, int *outobj, int *okr );
  56.     int    finddef( OBJECT *tree, int obj );
  57.     void    move_csr( OBJECT *tree, int editobj, int *okr, int *outobj );
  58.     int    findtab( OBJECT *tree, int obj );
  59.     /* 
  60.      * Souris: 
  61.      */
  62.     int    form_dobutton( OBJECT *tree, int obj, int mouse_x, int clicks, int *nextobj, int *hotobj, int *ob_neweditx );
  63.     void    doradio( OBJECT *tree, int obj );
  64.  
  65.    
  66.    
  67. /*
  68.  * ------------------------ CONSTANTES -------------------------
  69.  */
  70.     #define    M1ENTER    0
  71.     #define    M1EXIT    1
  72.  
  73.  
  74.  
  75. /*
  76.  * ------------------------ VARIABLES -------------------------
  77.  */
  78.  
  79. /*
  80.  * External variables: 
  81.  */
  82.     /*
  83.      * Config: 
  84.      */
  85.     extern    int        G_cnf_gest_form_std;    /* Gestion de formulaires Standard */
  86.  
  87.  
  88. /*
  89.  * Private variables: 
  90.  */
  91.     /*
  92.      * Pour rectangle d'attente sans hotspot: 
  93.      */
  94.     static    GRECT    M_brrect;
  95.     static    int    M_brmx, M_brmy, M_brtogl;                    /* Maptree */
  96.     /*
  97.      * Pour objet ‚ditable: 
  98.      */
  99.     static    int    M_fnobj, M_fnlast, M_fnprev, M_fndir;        /* Maptree */
  100.     /* 
  101.      * DerniŠre position souris: 
  102.      */
  103.     static    int    M_mouse_x, M_mouse_y;
  104.      
  105.  
  106. /*
  107.  * ------------------------ FUNCTIONS -------------------------
  108.  */
  109.  
  110. /*
  111.  * ext_form_do(-)
  112.  *
  113.  * Purpose:
  114.  * --------
  115.  * Appelle gestion standard ou ‚tendue selon config
  116.  *
  117.  * History:
  118.  * --------
  119.  * 1993: fplanque: Created
  120.  */
  121. int    ext_form_do( OBJECT *tree, int *startfield )
  122. {    /*
  123.      * Si pas d'objet ‚ditable, *startfield devrait ˆtre nul 
  124.      */
  125.     /* 
  126.      * Teste si on veut une gestion standard ou ‚tendue: 
  127.      */
  128.     if ( G_cnf_gest_form_std )
  129.     {    /*
  130.          * Gestion de formulaires Standard: 
  131.          */
  132.         int    exit_obj;
  133.         int    m_button;        /* Place holder */
  134.         
  135.         exit_obj = form_do( tree, *startfield );
  136.         
  137.         /*
  138.          * D‚termine coordonn‚es de la souris 
  139.          * lorsqu'on quitte le formulaire: 
  140.          */
  141.         vq_mouse( G_ws_handle, &m_button, &M_mouse_x, &M_mouse_y );
  142.         
  143.         return    exit_obj;
  144.     }
  145.     else
  146.     {    /*
  147.          * Gestion ‚tendue: 
  148.          */
  149.         return    ext_form_gest( tree, startfield, FALSE0 );
  150.     }
  151. }
  152.  
  153.  
  154. /*
  155.  * ext_form_gest(-)
  156.  *
  157.  * Purpose:
  158.  * --------
  159.  * Gestion de Form_do ‚tendue
  160.  *
  161.  * History:
  162.  * --------
  163.  * 1993: fplanque: Created
  164.  */
  165. int    ext_form_gest(
  166.             OBJECT *    tree, 
  167.             int      *    startfield, 
  168.             int         allow_outside )
  169. {
  170.  
  171.     /*
  172.      * Variables locales: 
  173.      */
  174.     /* Edition: */
  175.     int    editobj;        /* No de l'objet sur lequel est plac‚ le curseur */
  176.                             /* Donc celui auquel s'adresse le clavier */
  177.     int    nextobj;        /* Objet sur lequel on a cliqu‚ avec la souris */
  178.                             /* Pourrait devenir le editobj si ‚ditable */
  179.     int    ob_editx;    /* Position du curseur dans champ d'‚dition */
  180.     int    ob_neweditx=-1;    /* Prochaine position */
  181.     /* Hotspot: */
  182.     int    hotmode;        /* =M1ENTER: la souris est hors du formulaire */
  183.                             /* =M1EXIT:  la souris est dedans */
  184.     int    hotobj;        /* No de l'objet "HOT" actif ou -1 */
  185.     GRECT    hotrect;        /* Rectangle d'attente souris courant */
  186.     /* Gestion des ‚venements: */
  187.     int    which;        /* Evenement produit */
  188.     int    cont;            /* =-1 tant qu'on a pas d‚cid‚ de quitter */
  189.     int    mb, ks, kr, br;
  190.     /*    int    (*valid)(); */
  191.         
  192.     /* Initialisation ‚dition: */
  193.     nextobj = *startfield;
  194.     editobj = 0;
  195.     
  196.     /* Conditions de hotspot initiales: */
  197.     hotobj = -1;
  198.     hotmode = M1ENTER;
  199.     objc_xywh( tree, 0, &hotrect );
  200.  
  201.     /* Boucle pple: */
  202.     cont = TRUE_1;
  203.     while( cont )
  204.     {
  205.         /*
  206.          * Positionne curseur sur le champ s‚lectionn‚: 
  207.          */
  208.         if ( editobj != nextobj && nextobj != 0 )
  209.         {
  210.             editobj = nextobj;    /* Nouvel objet ‚ditable */
  211.             nextobj = 0;            /* Pas encore d'autre demande! */
  212.             objc_edit( tree, editobj, 0, &ob_editx, ED_INIT );
  213.         }
  214.  
  215.         /*
  216.          * S'il faut modifier la position du curseur: 
  217.          */
  218.         if ( ob_neweditx != -1 )
  219.         {
  220.             if ( ob_editx != ob_neweditx )
  221.             {
  222.                 objc_edit( tree, editobj, 0, &ob_editx, ED_END );    /* Efface csr */
  223.                 ob_editx = ob_neweditx;        /* Nouvelle position */
  224.                 objc_edit( tree, editobj, 0, &ob_editx, ED_CHAR ); /* Positionne csr */
  225.                 objc_edit( tree, editobj, 0, &ob_editx, ED_END ); /* Affiche csr */
  226.             }
  227.             ob_neweditx = -1;
  228.         }
  229.         
  230.         /*
  231.          * Attend ‚venement 
  232.          */
  233.         which = evnt_multi( MU_KEYBD | MU_BUTTON | MU_M1,
  234.                             2, 1, 1,
  235.                             hotmode, hotrect .g_x, hotrect .g_y, hotrect .g_w, hotrect .g_h,
  236.                             0, 0, 0, 0, 0,
  237.                             NULL,
  238.                             0, 0,
  239.                             &M_mouse_x, &M_mouse_y, &mb,
  240.                             &ks, &kr,
  241.                             &br );
  242.     
  243.         /*
  244.          * Hotspot: 
  245.          */
  246.         if ( which & MU_M1 )
  247.             hotobj = form_dohot( tree, hotobj, M_mouse_x, M_mouse_y, &hotrect, &hotmode);
  248.  
  249.         /*
  250.          * Clavier: 
  251.          */
  252.         if ( which & MU_KEYBD )
  253.         {
  254.             /*
  255.              * Filtrage des touches sp‚ciales: 
  256.              */
  257.             cont = form_dokeybd( tree, editobj, kr, ks, &nextobj, &kr );
  258.             /*
  259.              * Traite autres caractŠres normalement: 
  260.              */
  261.             if( kr && editobj )
  262.             {
  263.                 objc_edit( tree, editobj, kr, &ob_editx, ED_CHAR );
  264.             }
  265.         }
  266.         
  267.         /*
  268.          * Clics souris: 
  269.          */
  270.         if( which & MU_BUTTON )
  271.         {
  272.             /*
  273.              * Trouve l'objet sur lequel on a cliqu‚: 
  274.              */
  275.             nextobj = objc_find( tree, 0, 5, M_mouse_x, M_mouse_y );
  276.             if ( nextobj == -1 )
  277.             {    /*
  278.                  * On a cliqu‚ hors du formulaire: 
  279.                  * Teste s'il faut en tenir compte: 
  280.                  */
  281.                 if( allow_outside )
  282.                 {    /*
  283.                      * Si on doit prendre en compte un clic … l'ext‚rieur: 
  284.                      */
  285.                     cont = FALSE0;        /* On interprŠte ‡a comme une Annulation */
  286.                 }
  287.                 else
  288.                 {    /*
  289.                      * Si on doit ignorer les clics … l'ext‚rieur:
  290.                      */
  291.                     nextobj = 0;
  292.                 }
  293.             }
  294.             else
  295.             {    /*
  296.                  * Traite le clic: 
  297.                  */
  298.                 cont = form_dobutton( tree, nextobj, M_mouse_x, br, &nextobj, &hotobj, &ob_neweditx );
  299.             }
  300.         }
  301.  
  302.         /*
  303.          * Teste s'il faut effacer le curseur: 
  304.          */
  305.         if (     !cont 
  306.             ||    (    nextobj != editobj
  307.                 &&    nextobj    != 0
  308.                 )
  309.             )
  310.         {
  311.             objc_edit( tree, editobj, 0, &ob_editx, ED_END );
  312.         }
  313.     }
  314.  
  315.     /*
  316.      * Teste s'il faut enlever HOTSPOT (en cas de pression sur Return ) 
  317.      */
  318.     if ( hotobj != (nextobj & 0x7FFF) )
  319.     {
  320.         if ( hotobj != -1 )
  321.             objc_toggle( tree, hotobj );
  322.     }
  323.                     
  324.     /*
  325.      * Fin 
  326.      */
  327.     *startfield = editobj;        /* Objet en cours d'‚dition */
  328.     return    nextobj;                /* Objet cliqu‚ */
  329. }
  330.  
  331.   
  332. /*
  333.  * ------------------ GESTION DES HOT-SPOTS -----------------
  334.  */                                   
  335.  
  336.   
  337. /*
  338.  * form_dohot(-)
  339.  *
  340.  * Purpose:
  341.  * --------
  342.  * Traitement des Hot Spots
  343.  *
  344.  * History:
  345.  * --------
  346.  * fplanque: Created
  347.  */
  348. int    form_dohot( OBJECT *tree, int hotobj, int M_mouse_x, int M_mouse_y, GRECT *rect, int *mode )
  349. {
  350.     GRECT    root;
  351.     int    state;
  352.  
  353.     /*
  354.      * Trouve coordonn‚es de la boite pple: 
  355.      */
  356.     objc_xywh( tree, 0, &root );
  357.     
  358.     /*
  359.      * S'il y a d‚j… un objet "allum‚", on l'‚teind: 
  360.      */
  361.     if ( hotobj != -1 )
  362.     {
  363.         objc_toggle( tree, hotobj );
  364.     }
  365.             
  366.     /*
  367.      * Si la souris est sortie du form: 
  368.      */
  369.     if ( !(inside( M_mouse_x, M_mouse_y, &root ) ) )
  370.     {
  371.         *mode = M1ENTER;
  372.         *rect = root;
  373.         return -1;
  374.     }
  375.         
  376.     /*
  377.      * Sinon, sur quel objet se trouve-t-on?: 
  378.      */
  379.     hotobj = objc_find( tree, 0, 6, M_mouse_x, M_mouse_y );
  380.     /* printf("Object: %d \n", hotobj); */
  381.         
  382.     /*
  383.      * S'agit-il d'un hotspot?: 
  384.      */
  385.     state = tree[ hotobj ] .ob_state;
  386.     /* printf("Obj flags=%X (selectable=%X) -> %X    \n", tree[ hotobj ] .ob_flags, SELECTABLE, ( tree[ hotobj ] .ob_flags & SELECTABLE ) ); */
  387.     if ( tree[ hotobj ] .ob_flags & SELECTABLE )
  388.     {
  389.         if ( !(state & DISABLED) )
  390.         {    /* Oui, c'est un hot spot... … allumer! */
  391.             *mode = M1EXIT;    /* On le changera qd on ressortira */
  392.             objc_xywh( tree, hotobj, rect );
  393.             /*
  394.              * On va le mettre en inverse vid‚o 
  395.              * s'il n'est pas d‚j… s‚lectionn‚: 
  396.              */
  397.             if ( state & SELECTED )
  398.             {    /*
  399.                  * Si d‚j… s‚lectionn‚, on ne fait rien: 
  400.                  */
  401.                 return -1;
  402.             }
  403.             else
  404.             {
  405.                 objc_toggle( tree, hotobj );
  406.                 return hotobj;
  407.             }
  408.         }
  409.     }
  410.     
  411.     /* 
  412.      * Pas d'objet hotspot ss le curseur, alors calcule rectangle
  413.      *    qui nous int‚resse pour en trouver: 
  414.      */
  415.     M_brrect = root;
  416.     M_brmx = M_mouse_x;        /* Sauve coordonn‚es de la souris */
  417.     M_brmy = M_mouse_y;
  418.     M_brtogl = 0;
  419.     maptree( tree, 0, -1, breakobj );
  420.     *rect = M_brrect;
  421.     *mode = M1EXIT;
  422.     return -1;
  423. }
  424.  
  425.  
  426.  
  427. /*
  428.  * breakobj(-)
  429.  *
  430.  * Purpose:
  431.  * --------
  432.  * utilisé par form_dohot
  433.  *
  434.  * History:
  435.  * --------
  436.  * fplanque: Created
  437.  */
  438. int    breakobj( OBJECT *tree, int obj )
  439. {
  440.     GRECT    s;
  441.     int    flags, broken, pxy[4];
  442.     
  443.     objc_xywh( tree, obj, &s );
  444.     grecttoarray( &s, pxy );
  445.     if ( !grcintersect(&M_brrect, &s) )
  446.     {    /*
  447.          * Si l'objet test‚ est hors du rectangle de mouvement actuel: 
  448.          */
  449.         return    0;            /* On l'ignore et ses enfants avec... */
  450.     }
  451.         
  452.     /* 
  453.      * Teste les flags de l'objt pour voir s'il peut etre selectionne,
  454.      * Donc s'il peut passer au hot-spot, Dans le cas contraire, on va
  455.      * l'ignorer car il ne constituera pas la frontiŠre de la zone libre
  456.      * sans hot spots...
  457.      */
  458.     flags = tree[ obj ] .ob_flags;
  459.         
  460.     if ( flags & HIDETREE )
  461.     {    /*
  462.          * Si l'objet test‚ … ‚t‚ cach‚: 
  463.          */
  464.         return    0;            /* On l'ignore et ses enfants avec... */
  465.     }
  466.     
  467.     if ( !(flags & SELECTABLE) )
  468.     {    /*
  469.          * Si l'objet test‚ n'est pas s‚lectionnable (-> ps de Hot-Spot): 
  470.          */
  471.         return    -1;            /* On l'ignore mais pas ses enfants */
  472.     }
  473.     
  474.     if ( tree[ obj ] .ob_state & DISABLED )
  475.     {    /*
  476.          * Si l'objet test‚ est DISABLED: 
  477.          */
  478.         return    -1;            /* On l'ignore mais pas ses enfants */
  479.     }
  480.  
  481.     /*
  482.      * Arriv‚ ici, il y a un objet s‚lectionnable dans le rectangle
  483.      * de d‚limitation de la zone sans hot-spots; il va donc falloir 
  484.      * la r‚duire: BREAK
  485.      */
  486.     if (M_brtogl)
  487.     {
  488.         broken = breakx( pxy );
  489.         if ( !broken )
  490.         {
  491.             broken = breaky( pxy );
  492.         }
  493.     }
  494.     else
  495.     {
  496.         broken = breaky(pxy);
  497.         if ( !broken )
  498.         {
  499.             broken = breakx( pxy );
  500.         }
  501.     }
  502.  
  503.     M_brtogl = !M_brtogl;            /* Permet d'alterner les coupures verticales/horizontales */
  504.     
  505.     /* Emergency TEST:
  506.      * Si jamais le pointeur de la souris se rentrouve dans le rectangle
  507.      * de l'objet … exclure du rect de mvt de la souris!
  508.      * Ceci peut se produire dans 2 cas:
  509.      * - Il y a un objet non selectionnable inclus dans un s‚lectionnable
  510.      * - On tourne sous AES 4.0 pour lequel OBJC_FIND merdouille un peu!
  511.      */
  512.     if ( !broken )
  513.     {    /* 
  514.          * Si on n'a pas pu couper en X ni en Y: 
  515.          */
  516.         /*    ping(); */
  517.         M_brrect .g_x = M_brmx;        /* R‚duit zone de mvt … un seul point */
  518.         M_brrect .g_y = M_brmy;
  519.         M_brrect .g_w    = M_brrect .g_h = 1;
  520.     }
  521.     
  522.     return TRUE_1;
  523. }
  524.  
  525.  
  526.  
  527. /*
  528.  * breakx(-)
  529.  *
  530.  * Purpose:
  531.  * --------
  532.  * Essaye de couper le rectangle d'attente verticalement
  533.  *
  534.  * History:
  535.  * --------
  536.  * fplanque: Created
  537.  */
  538. int    breakx( int *pxy )
  539. {
  540.     if ( M_brmx < pxy[ 0 ] )
  541.     {    /*
  542.          * Si l'objet est … droite de la souris: 
  543.          */
  544.         M_brrect .g_w = pxy[ 0 ] - M_brrect .g_x;    /* Coupe … droite */
  545.         return    TRUE_1;        /* OK, c'est coup‚ */
  546.     }
  547.     
  548.     if ( M_brmx > pxy[ 2 ] )
  549.     {    /*
  550.          * Si l'objet est … gauche de la souris: 
  551.          */
  552.         M_brrect .g_w += M_brrect .g_x - pxy[ 2 ] -1;    /* Coupe … gauche */
  553.         M_brrect .g_x = pxy[ 2 ] +1;
  554.         return    TRUE_1;        /* OK, c'est coup‚ */
  555.     }
  556.         
  557.     return    FALSE0;    /* On n'a PAS pu couper! */
  558. }
  559.  
  560.  
  561.  
  562. /*
  563.  * breaky(-)
  564.  *
  565.  * Purpose:
  566.  * --------
  567.  * Essaye de couper le rectangle d'attente horizontalement
  568.  *
  569.  * History:
  570.  * --------
  571.  * fplanque: Created
  572.  */
  573. int    breaky( int *pxy )
  574. {
  575.     if ( M_brmy < pxy[ 1 ] )
  576.     {    /*
  577.          * Si l'objet est au dessous de la souris: 
  578.          */
  579.         M_brrect .g_h = pxy[ 1 ] - M_brrect .g_y;    /* Coupe en bas */
  580.         return    TRUE_1;        /* OK, c'est coup‚ */
  581.     }
  582.     
  583.     if ( M_brmy > pxy[ 3 ] )
  584.     {    /*
  585.          * Si l'objet est au dessus de la souris: 
  586.          */
  587.         M_brrect .g_h += M_brrect .g_y - pxy[ 3 ] -1;    /* Coupe en haut */
  588.         M_brrect .g_y = pxy[ 3 ] +1;
  589.         return    TRUE_1;        /* OK, c'est coup‚ */
  590.     }
  591.     
  592.     return  FALSE0;    /* On n'a pas pu couper */
  593. }
  594.  
  595.  
  596. /*
  597.  * inside(-)
  598.  *
  599.  * Purpose:
  600.  * --------
  601.  * D‚termine si un point est … l'int‚rieur d'un rectangle ou non
  602.  *
  603.  * History:
  604.  * --------
  605.  * fplanque: Created
  606.  */
  607. int inside( int x, int y, GRECT *pt )
  608. {
  609.     if (     ( x >= pt -> g_x ) && ( y >= pt -> g_y )
  610.         &&    ( x < pt -> g_x + pt -> g_w ) && ( y < pt -> g_y + pt -> g_h ) )
  611.     {
  612.         return -1;
  613.     }
  614.     else
  615.     {
  616.         return 0;
  617.     }
  618. }
  619.  
  620.  
  621.    
  622. /*
  623.  * ------------------------ CLAVIER -------------------------
  624.  */
  625.  
  626.  
  627. /*
  628.  * form_dokeybd(-)
  629.  *
  630.  * Purpose:
  631.  * --------
  632.  * Form_Keybd
  633.  *
  634.  * History:
  635.  * --------
  636.  * 1993: fplanque: Created
  637.  * 14.12.94: correction bug chp prec/chp suivant
  638.  */
  639. int    form_dokeybd( 
  640.             OBJECT *    tree, 
  641.             int         editobj, 
  642.             int         kr, 
  643.             int         keystate, 
  644.             int     *    outobj, 
  645.             int     *    okr )
  646. {
  647.     char    low    = (char) kr;        /* Low byte */
  648.  
  649.     M_fndir = 1;            /* Direction TAB par d‚faut: AVANCE */
  650.  
  651.     /* printf("\r %X %X ", kr, keystate); */
  652.  
  653.     if( low )
  654.     {    /*
  655.          * Si valide 
  656.          * On ne s'int‚resse plus k'… ‡a:
  657.          */
  658.         kr = low;
  659.         
  660.         switch( kr )
  661.         {
  662.             case    CR:
  663.                 *okr = 0;
  664.                 M_fnobj = -1;
  665.                 maptree( tree, 0, -1, finddef );
  666.                 if (M_fnobj != -1 )
  667.                 {
  668.                     objc_sel( tree, M_fnobj );
  669.                     *outobj = M_fnobj;
  670.                     return 0;
  671.                 }
  672.                 /* Si pas d'objet default */
  673.                 move_csr( tree, editobj, okr, outobj );    /* Cherche champ suivant*/
  674.                 break;        
  675.             
  676.             case    TAB:
  677.                 if ( keystate & 0x0003 )
  678.                 {    /* Si touche Shift press‚e */
  679.                     M_fndir = 0;                    /* Direction dir: ARRIERE */
  680.                 }
  681.                 move_csr( tree, editobj, okr, outobj );    /* Cherche champ suivant/pr‚c‚dent */
  682.                 break;
  683.         }
  684.  
  685.         return    -1;
  686.     }                
  687.  
  688.     /*
  689.      * On doit interpr‚ter le SCAN CODE
  690.      */
  691.     switch( kr >> 8 )
  692.     {
  693.         case    STSCAN_UP:
  694.             M_fndir    = 0;                        /* Direction dir: ARRIERE */
  695.         case    STSCAN_DOWN:
  696.             move_csr( tree, editobj, okr, outobj );    /* Cherche champ */
  697.             break;
  698.     }
  699.  
  700.     return -1;
  701. }
  702.  
  703.  
  704.  
  705. /*
  706.  * finddef(-)
  707.  *
  708.  * Purpose:
  709.  * --------
  710.  * Finddef appel‚ par form_dokeybd()
  711.  *
  712.  * History:
  713.  * --------
  714.  * fplanque: Created
  715.  */
  716. int    finddef( OBJECT *tree, int obj )
  717. {
  718.     int    ob_flags = tree[ obj ] .ob_flags;
  719.  
  720.     if ( ob_flags & HIDETREE )
  721.         return 0;
  722.         
  723.     if ( ob_flags & DEFAULT )
  724.         if( !( tree[ obj ] .ob_state & DISABLED ) )
  725.             M_fnobj = obj;
  726.  
  727.     return    -1;
  728.  
  729. }
  730.  
  731.  
  732.  
  733. /*
  734.  * move_csr(-)
  735.  *
  736.  * Purpose:
  737.  * --------
  738.  * Provoque la recherche du champ ‚ditable suivant/pr‚c‚dent
  739.  *
  740.  * History:
  741.  * --------
  742.  * fplanque: Created
  743.  */
  744. void    move_csr( OBJECT *tree, int editobj, int *okr, int *outobj )
  745. {
  746.     *okr = 0;                        /* La touche press‚e est une touche de contr“le */
  747.  
  748.     M_fnlast = editobj;                /* Initialise recherche */
  749.     M_fnprev = M_fnobj = -1;
  750.  
  751.     maptree( tree, 0, -1, findtab);    /* Troube le champ recherch‚ */
  752.  
  753.     if ( M_fnobj == -1 )            /* Try to wrap around */
  754.         maptree( tree, 0, -1, findtab );
  755.  
  756.     if ( M_fnobj != -1 )            /* Si on a trouv‚ un nouvel objet */
  757.         *outobj = M_fnobj;                /* On s'y place */
  758. }
  759.  
  760.  
  761.  
  762. /*
  763.  * findtab(-)
  764.  *
  765.  * Purpose:
  766.  * --------
  767.  * description
  768.  *
  769.  * History:
  770.  * --------
  771.  * fplanque: Created
  772.  */
  773. int    findtab( OBJECT *tree, int obj )
  774. {
  775.     int    ob_flags = tree[ obj ] .ob_flags;
  776.  
  777.     if ( ob_flags & HIDETREE )
  778.         return 0;
  779.         
  780.     if ( !(ob_flags & EDITABLE) )
  781.         return 1;
  782.         
  783.     if ( M_fndir && M_fnprev == M_fnlast )
  784.         M_fnobj = obj;
  785.         
  786.     if ( !M_fndir && obj == M_fnlast )
  787.         M_fnobj = M_fnprev;
  788.         
  789.     M_fnprev = obj;
  790.     
  791.     return    -1;
  792. }
  793.  
  794.  
  795.  
  796.    
  797. /*
  798.  * --------------------- CLICKS SOURIS ---------------------
  799.  */
  800.  
  801.  
  802.  
  803. /*
  804.  * form_dobutton(-)
  805.  *
  806.  * Purpose:
  807.  * --------
  808.  * Form_button
  809.  *
  810.  * History:
  811.  * --------
  812.  * fplanque: Created
  813.  */
  814. int    form_dobutton( OBJECT *tree, int obj, int M_mouse_x, int clicks, int *nextobj, int *hotobj, int *ob_neweditx )
  815. {
  816.     int    flags = tree[ obj ] .ob_flags;
  817.     int    state = tree[ obj ] .ob_state;
  818.     int    texit = flags & TOUCHEXIT;
  819.     int    sble    = flags & SELECTABLE;
  820.     int    dsbld    = state & DISABLED;
  821.     int    edit    = flags & EDITABLE;
  822.     int    hibit = 0;                        /* Par d‚faut */
  823.     int    instate;
  824.  
  825.     /* printf("Click! "); */
  826.  
  827.     if ( !texit && (!sble || dsbld) && !edit )
  828.     {
  829.         /* printf("Ya cant't click here!\n"); */
  830.         /* ping(); */
  831.         *nextobj = 0;
  832.         return    -1;
  833.     }
  834.     
  835.     if ( texit && clicks == 2 )
  836.     {
  837.         hibit = 0x8000;
  838.     }
  839.     
  840.     if ( sble && !dsbld )
  841.     {
  842.         if ( flags & RBUTTON )
  843.             doradio( tree, obj );
  844.         else if ( !texit )
  845.         {
  846.             instate = ( obj == *hotobj)? state: state^SELECTED;
  847.             if ( !graf_watchbox(tree, obj, instate, instate^SELECTED ) )
  848.             {    /* Si l'utilisateur … abandonn‚ */
  849.                 ping();
  850.                 *nextobj = 0;
  851.                 *hotobj    = NIL;
  852.                 return    TRUE_1;
  853.             }
  854.         }
  855.         else    /* if (texit) */
  856.                 if (obj != *hotobj )
  857.                     objc_toggle( tree, obj );
  858.     }
  859.     
  860.     if ( obj == *hotobj )
  861.         *hotobj = -1;
  862.         
  863.     if ( texit || (flags & EXIT) )
  864.     {     /* Si le bouton conduit … abandonner le formulaire: */
  865.         /* printf("****\rEXIT\r"); */
  866.         *nextobj = obj | hibit;
  867.         return FALSE0;
  868.     }
  869.     else
  870.     {
  871.         if ( edit )
  872.         {    /* Si on a cliqu‚ sur un objet ‚ditable: */
  873.             TEDINFO    *tedinfo    = tree[ obj ] .ob_spec.tedinfo;    /* Ptr sur TEDINFO */
  874.             char        *ptext    = tedinfo -> te_ptext;                /* Ptr sur TEXTE */
  875.             char        *ptemp    = tedinfo -> te_ptmplt;                /* Ptr sur MASQUE */
  876.             int        temp_length;                /* Longueur du masque */
  877.             int        temp_width;                    /* Largeur du masque en pixels */
  878.             int        ob_x, ob_y;                    /* Coordonn‚es de l'objet */
  879.             int        temp_offset;
  880.             int        click_offset;
  881.             int        new_pos = -1;
  882.             int        i = 0;
  883.             
  884.             /* ping(); */
  885.  
  886.             /*
  887.              * Coordonn‚es absolues de l'objet: 
  888.              */
  889.             objc_offset( tree, obj, &ob_x, &ob_y );
  890.         
  891.             /*
  892.              * Longueur du masque: 
  893.              */
  894.             temp_length = (int) strlen( ptemp );
  895.             temp_width    = temp_length * G_std_text .cell_w;
  896.             /*
  897.              * Diff‚rence de largeur 
  898.              */
  899.             temp_offset = tree[ obj ] .ob_width - temp_width;
  900.  
  901.             /*
  902.              * Offset X du click dans l'objet 
  903.              */
  904.             click_offset = M_mouse_x - ob_x;
  905.             /* 
  906.              * A modifier en fonction du "centrage" du texte: 
  907.              */
  908.             switch( tedinfo -> te_just )
  909.             {
  910.                 case    1:        /* Justifi‚ … droite: */
  911.                     click_offset -= temp_offset;
  912.                     break;
  913.                     
  914.                 case    2:        /* Centr‚: */
  915.                     click_offset -= temp_offset/2;
  916.                     break;
  917.             }
  918.             /*    printf("W=%d Click=%d/%d ",temp_width, click_offset, G_std_text.cell_w); */
  919.  
  920.             /*
  921.              * Cherche position dans le texte: 
  922.              */
  923.             while( i <= temp_length )
  924.             {    /*
  925.                  * Parcourt le masque jusqu'… la position du click 
  926.                  */
  927.                 if ( i * G_std_text .cell_w > click_offset )
  928.                 {    /* Si on a d‚pass‚ le click */
  929.                     break;
  930.                 }
  931.  
  932.                 if ( ptemp[ i ] == '_' )
  933.                 {    /* Si on a pass‚ un emplacement texte: */
  934.                     new_pos++;
  935.                 }
  936.  
  937.                 i++;
  938.             }
  939.  
  940.             /*
  941.              * Masque la position demand‚e sur l'intervalle des possibles 
  942.              */
  943.             *ob_neweditx = max( 0, min( (int)strlen( ptext ), new_pos ) );
  944.             /*    printf("New x=%d\r",*ob_neweditx); */
  945.         }
  946.         else
  947.         {    /*
  948.              * On a pas cliqu‚ sur un ‚ditable 
  949.              */
  950.             *nextobj = 0;
  951.         }
  952.     }    
  953.  
  954.     /* printf("\r"); */
  955.     return -1;
  956. }
  957.  
  958.  
  959.  
  960. /*
  961.  * doradio(-)
  962.  *
  963.  * Purpose:
  964.  * --------
  965.  * Pour les radio-buttons
  966.  *
  967.  * History:
  968.  * --------
  969.  * fplanque: Created
  970.  */
  971. void    doradio( OBJECT *tree, int obj )
  972. {
  973.     GRECT    root;
  974.     int    pobj, sobj;
  975.  
  976.     objc_xywh( tree, 0, &root );
  977.     pobj = objc_parent( tree, obj );
  978.     for ( sobj = tree[ pobj ] .ob_head;        /* D‚but: 1er enfant */
  979.             sobj != pobj;                            /* Jusqu'… ce qu'on revienne au pŠre */
  980.             sobj = tree[ sobj ] .ob_next )    /* Passe … l'obj suivant */
  981.     {
  982.         if ( sobj != obj )
  983.         {    /* Si pas l'objet sur lequel on … cliqu‚: */
  984.             objc_dsel( tree, sobj );
  985.         }
  986.     }
  987.     objc_sel( tree, obj );    /* Sel objet cliqu‚ au cas ou pas encore fait */
  988. }
  989.  
  990.  
  991.    
  992.    
  993. /*
  994.  * ------------------------ DIVERS -------------------------
  995.  */
  996.  
  997.  
  998.  
  999. /*
  1000.  * extform_lastmpos(-)
  1001.  *
  1002.  * Purpose:
  1003.  * --------
  1004.  * DerniŠre position de la souris
  1005.  *
  1006.  * History:
  1007.  * --------
  1008.  * fplanque: Created
  1009.  */
  1010. void    extform_lastmpos( int *mx, int *my )
  1011. {
  1012.     *mx = M_mouse_x;
  1013.     *my = M_mouse_y;
  1014. }